From 8756deec5898c281b88aeb546fe769e55b126f6b Mon Sep 17 00:00:00 2001 From: Benjamin Otte Date: Thu, 8 Dec 2016 21:14:41 +0100 Subject: [PATCH] vulkan: Turn swapchain image targets into GskVulkanImages This gives us proper refcounting here, too. And there's no longer a difference between the different types of images. --- gsk/gskvulkanimage.c | 43 +++++++++++++++++++++----- gsk/gskvulkanimageprivate.h | 5 +++ gsk/gskvulkanrenderer.c | 61 +++++++++++++++---------------------- 3 files changed, 65 insertions(+), 44 deletions(-) diff --git a/gsk/gskvulkanimage.c b/gsk/gskvulkanimage.c index 9ba7451267..b82398d276 100644 --- a/gsk/gskvulkanimage.c +++ b/gsk/gskvulkanimage.c @@ -109,14 +109,15 @@ gsk_vulkan_image_upload_data (GskVulkanImage *self, } static void -gsk_vulkan_image_ensure_view (GskVulkanImage *self) +gsk_vulkan_image_ensure_view (GskVulkanImage *self, + VkFormat format) { GSK_VK_CHECK (vkCreateImageView, gdk_vulkan_context_get_device (self->vulkan), &(VkImageViewCreateInfo) { .sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO, .image = self->vk_image, .viewType = VK_IMAGE_VIEW_TYPE_2D, - .format = VK_FORMAT_B8G8R8A8_SRGB, + .format = format, .components = { .r = VK_COMPONENT_SWIZZLE_R, .g = VK_COMPONENT_SWIZZLE_G, @@ -261,7 +262,7 @@ gsk_vulkan_image_new_from_data_via_staging_image (GdkVulkanContext *context, /* XXX: Is this okay or do we need to keep the staging image around until the commands execute */ g_object_unref (staging); - gsk_vulkan_image_ensure_view (self); + gsk_vulkan_image_ensure_view (self, VK_FORMAT_B8G8R8A8_SRGB); return self; } @@ -311,7 +312,7 @@ gsk_vulkan_image_new_from_data_directly (GdkVulkanContext *context, } }); - gsk_vulkan_image_ensure_view (self); + gsk_vulkan_image_ensure_view (self, VK_FORMAT_B8G8R8A8_SRGB); return self; } @@ -330,6 +331,27 @@ gsk_vulkan_image_new_from_data (GdkVulkanContext *context, return gsk_vulkan_image_new_from_data_directly (context, command_buffer, data, width, height, stride); } +GskVulkanImage * +gsk_vulkan_image_new_for_swapchain (GdkVulkanContext *context, + VkImage image, + VkFormat format, + gsize width, + gsize height) +{ + GskVulkanImage *self; + + self = g_object_new (GSK_TYPE_VULKAN_IMAGE, NULL); + + self->vulkan = g_object_ref (context); + self->width = width; + self->height = height; + self->vk_image = image; + + gsk_vulkan_image_ensure_view (self, VK_FORMAT_B8G8R8A8_SRGB); + + return self; +} + void gsk_vulkan_image_finalize (GObject *object) { @@ -342,11 +364,16 @@ gsk_vulkan_image_finalize (GObject *object) NULL); } - gsk_vulkan_memory_free (self->memory); + /* memory is NULL for for_swapchain() images, where we don't own + * the VkImage */ + if (self->memory) + { + gsk_vulkan_memory_free (self->memory); - vkDestroyImage (gdk_vulkan_context_get_device (self->vulkan), - self->vk_image, - NULL); + vkDestroyImage (gdk_vulkan_context_get_device (self->vulkan), + self->vk_image, + NULL); + } g_object_unref (self->vulkan); diff --git a/gsk/gskvulkanimageprivate.h b/gsk/gskvulkanimageprivate.h index 9b02893988..1c43d9aa9b 100644 --- a/gsk/gskvulkanimageprivate.h +++ b/gsk/gskvulkanimageprivate.h @@ -9,6 +9,11 @@ G_BEGIN_DECLS G_DECLARE_FINAL_TYPE (GskVulkanImage, gsk_vulkan_image, GSK, VULKAN_IMAGE, GObject) +GskVulkanImage * gsk_vulkan_image_new_for_swapchain (GdkVulkanContext *context, + VkImage image, + VkFormat format, + gsize width, + gsize height); GskVulkanImage * gsk_vulkan_image_new_from_data (GdkVulkanContext *context, VkCommandBuffer command_buffer, guchar *data, diff --git a/gsk/gskvulkanrenderer.c b/gsk/gskvulkanrenderer.c index 929ea9118d..fe7623b5a8 100644 --- a/gsk/gskvulkanrenderer.c +++ b/gsk/gskvulkanrenderer.c @@ -57,56 +57,37 @@ struct _GskVulkanRendererClass G_DEFINE_TYPE (GskVulkanRenderer, gsk_vulkan_renderer, GSK_TYPE_RENDERER) struct _GskVulkanTarget { - VkImage image; - VkImageView image_view; + GskVulkanImage *image; VkFramebuffer framebuffer; }; static GskVulkanTarget * gsk_vulkan_target_new_for_image (GskVulkanRenderer *self, - VkImage image) + VkImage image, + gsize width, + gsize height) { GskVulkanTarget *target; - GdkWindow *window; VkDevice device; device = gdk_vulkan_context_get_device (self->vulkan); - window = gdk_draw_context_get_window (GDK_DRAW_CONTEXT (self->vulkan)); target = g_slice_new0 (GskVulkanTarget); - target->image = image; - - GSK_VK_CHECK (vkCreateImageView, device, - &(VkImageViewCreateInfo) { - .sType = VK_STRUCTURE_TYPE_IMAGE_VIEW_CREATE_INFO, - .image = target->image, - .viewType = VK_IMAGE_VIEW_TYPE_2D, - .format = gdk_vulkan_context_get_image_format (self->vulkan), - .components = { - .r = VK_COMPONENT_SWIZZLE_R, - .g = VK_COMPONENT_SWIZZLE_G, - .b = VK_COMPONENT_SWIZZLE_B, - .a = VK_COMPONENT_SWIZZLE_A, - }, - .subresourceRange = { - .aspectMask = VK_IMAGE_ASPECT_COLOR_BIT, - .baseMipLevel = 0, - .levelCount = 1, - .baseArrayLayer = 0, - .layerCount = 1, - }, - }, - NULL, - &target->image_view); + target->image = gsk_vulkan_image_new_for_swapchain (self->vulkan, + image, + gdk_vulkan_context_get_image_format (self->vulkan), + width, height); GSK_VK_CHECK (vkCreateFramebuffer, device, &(VkFramebufferCreateInfo) { .sType = VK_STRUCTURE_TYPE_FRAMEBUFFER_CREATE_INFO, .renderPass = self->render_pass, .attachmentCount = 1, - .pAttachments = &target->image_view, - .width = gdk_window_get_width (window), - .height = gdk_window_get_height (window), + .pAttachments = (VkImageView[1]) { + gsk_vulkan_image_get_image_view (target->image) + }, + .width = width, + .height = height, .layers = 1 }, NULL, @@ -126,9 +107,8 @@ gsk_vulkan_target_free (GskVulkanRenderer *self, vkDestroyFramebuffer (device, target->framebuffer, NULL); - vkDestroyImageView (device, - target->image_view, - NULL); + + g_object_unref (target->image); g_slice_free (GskVulkanTarget, target); } @@ -151,6 +131,9 @@ static void gsk_vulkan_renderer_update_images_cb (GdkVulkanContext *context, GskVulkanRenderer *self) { + GdkWindow *window; + gint scale_factor; + gsize width, height; guint i; gsk_vulkan_renderer_free_targets (self); @@ -158,10 +141,16 @@ gsk_vulkan_renderer_update_images_cb (GdkVulkanContext *context, self->n_targets = gdk_vulkan_context_get_n_images (context); self->targets = g_new (GskVulkanTarget *, self->n_targets); + window = gsk_renderer_get_window (GSK_RENDERER (self)); + scale_factor = gdk_window_get_scale_factor (window); + width = gdk_window_get_width (window) * scale_factor; + height = gdk_window_get_height (window) * scale_factor; + for (i = 0; i < self->n_targets; i++) { self->targets[i] = gsk_vulkan_target_new_for_image (self, - gdk_vulkan_context_get_image (context, i)); + gdk_vulkan_context_get_image (context, i), + width, height); } } -- 2.30.2